const express = require('express')
// 日志工具
const morgan = require('morgan');

// 创建 express 的服务器实例
const app = express()
const joi = require('joi')
// 解析token
const expressJWT = require('express-jwt')
// 配置文件
const config = require('./src/utils/config')
// 工具包
const { isEqual, guid } = require('./src/utils/index')
// 数据库操作方法 
const { sqlOne } = require('./src/db/common')
// === 普通的控制台打印 ===
// 自定义日志格式
// morgan.format('joke', '[joke] :method :url :status');
// 选择指定格式
// app.use(morgan('joke'));

const { rolejudge } = require('./jurisdiction')
app.use('/uploads',express.static('uploads'));  
// write your code here...
app.get("/", (req, res) => {
  res.send("123")
})

var bodyParser = require("body-parser")
app.use(bodyParser.json()) // 解析json
app.use(bodyParser.urlencoded({ extended: false })) // 是否格式化表单


// const publicRouter = require('./src/rourer/publicRouter')
// const commemorateRoter = require("./src/rourer/commemorateRouter");
// // 导入 greatperson 路由 
// const greatpersonRoter = require("./src/rourer/greatpersonRouter");
// // 导入 property 路由
// const propertyRouter = require("./src/rourer/propertyRouter");

// 注册一个全局 处理失败中间件 
app.use((req, res, next) => {
  // const role = req.auth.role;
  // console.log(role);
  // console.log(req.method);
  console.log(req.body);
  console.log(req.url);
  // 生成时间戳
  // req.nowTime = new Date();
  // 所有路由都会先经过这个中间件  都会产生一个 res.cc 的函数 可以直接在后面进行调用
  res.onError = function (err = "服务出错，请稍后重试", status = 400) {
    res.send({
      status,
      // 判断err是字符串还是错误对象
      message: err instanceof Error ? err.message : err
    })
  }
  res.onSuccess = function (data, message = "成功", status = 200) {
    res.send({
      status,
      data,
      message
    })
  }


  // // 在这里判断是否需要分页
  // if (req.method.toLowerCase() === 'get' && req.query.pageSize && req.query.currentPage) {
  //   // 实现分页
  //   req.paging_query = true
  // } else {
  //   req.paging_query = false
  // }
  next()
})

// token验证中间件
app.use(expressJWT.expressjwt({ secret: config.jwtSecretKey, algorithms: ['HS256'] }).unless({ path: [/^\/public\//, /^\/user\//] }))

app.use((req,res,next)=>{
  console.log(req.auth);
  next()
})

// 挂载权限验证中间件
// app.use((req, res, next) => {
//   rolejudge(req,res,next);
//   // // req.token = req.headers.authorization;
//   // // console.log(req.token);
//   // // 判断token解析的数据中role的值
//   // console.log(req.auth);
//   // if (!req.auth) {
//   //   return next()
//   // }

//   // let flag = false; 
//   // // 验证通过
//   // for (let i in publicArr) {
//   //   const item = publicArr[i]
//   //   flag = item.test(req.path)
//   //   if (flag) break;
//   // }
//   // // console.log("flag=",flag);
//   // const _id = req.auth['_id']
//   // // console.log("_id",_id);
//   // if (flag) {
//   //   // 微信小程序段的token验证
//   //   if (!_id || _id.length==0) {
//   //     return res.onError("登录已过期，请重新登录！")
//   //   }
//   //   return next();
//   // }else {
//   //   if (_id.length>=0) {
//   //     return res.onError("登录已过期，请重新登录！")
//   //   }
//   // }
//   // const role = req.auth.role;
//   // if (role === 0) {
//   //   if (isEqual(req.method, "GET")) {
//   //     return next()
//   //   } else {
//   //     return res.onError("权限不足，无法操作")
//   //   }
//   // }
//   // return next()
//   // // 判断请求类型 
//   // // if(role===0&&req.method)
// })

// // === 实现数据库日志操作 ===
// // 自定义 token
// morgan.token('user', (req, res) => {
//   // 在这里定义你的自定义逻辑
//   return req.auth ? req.auth.username : null;
// });
// morgan.token('body', (req, res) => {
//   // 在这里定义你的自定义逻辑
//   return JSON.stringify(req.body || null).replace(/[\t\r\f\n\s]*/g,'');
// });
// morgan.format('joke', ':method :url :status :response-time :res[content-length] :user :body');
// const dbStream = {
//   write: function (line) {
//     console.log(line);
//     const arr = ['method', 'url', 'status', 'timeconsuming', 'reslength', 'user', 'body']
//     line = line.split(' ')
//     // console.log(line);
//     let obj = line.reduce((acc, curr, index) => {
//       acc[arr[index]] = curr;
//       return acc;
//     }, { id: guid(), time: new Date() });
//     // 存入数据库
//     sqlOne('insert into logs set ?', obj).then(res => {
//       // console.log(res);
//       if (res.affectedRows === 1) {
//         console.log('日志插入成功');
//       }
//     })
//     // console.log(obj);
//   }
// }
// app.use(morgan('joke', { stream: dbStream }));



// 挂载路由
// app.use('/public', publicRouter)
// app.use('/wechat', commemorateRoter)

// 导入user跟由
const userRouter = require("./src/rourer/userRouter");
const articleRouter = require("./src/rourer/articleRouter");
const uploadRouter = require("./src/rourer/uploadRouter");
const commentRouter = require("./src/rourer/commentRouter");
const replyRouter = require("./src/rourer/replyRouter");
const apiRouter = require("./src/rourer/apiRouter");


// /user用户公开接口
app.use('/user', userRouter)

// 需要授权接口
app.use('/api', articleRouter)
app.use('/api', apiRouter)
app.use('/api', replyRouter)
app.use('/api', commentRouter)
app.use('/api', uploadRouter)

// app.use('/api', commentRouter)
// app.use('/user',categoryRouter)
// app.use('/greatperson', greatpersonRoter)
// app.use('/property', propertyRouter)



// 错误中间件
app.use(function (err, req, res, next) {
  // console.log(req.body);
  console.log("===错误中间件指向===");
  if (err) {
    console.log("===============错误==================");
    console.log("err=", JSON.stringify(err));
    console.log("=====================================");
  }
  if (err.name === 'UnauthorizedError') return res.status(401).send({message:'登录过期，身份认证失败!'})
  // 数据验证失败
  if (err instanceof joi.ValidationError) {
    return res.status(500).send(err)
  }
  // 未知错误
  res.status(500).send(err)
})



// 调用 app.listen 方法，指定端口号并启动web服务器
app.listen(3000, function () {
  console.log('api server running at http://127.0.0.1:3000')
})
